using System;
using System.Windows;
using System.Data;
using System.Xml;
using System.Configuration;
using System.Diagnostics;
using System.Windows.Media.Imaging;
using System.IO;
using System.Windows.Controls;
using System.Reflection;
using Ricciolo.PaperBoy.Environment.ExceptionHandling;
using Ricciolo.PaperBoy.Environment.Properties;
using Ricciolo.PaperBoy.Themes.Classic;

namespace Ricciolo.PaperBoy.Environment
{
 
    public partial class Program : System.Windows.Application
    {

        private static Ricciolo.PaperBoy.UI.SplashScreen splashScreen;

        [STAThread()]
        static void Main()
        {
            splashScreen = new Ricciolo.PaperBoy.UI.SplashScreen();
            splashScreen.Show();

            Program app = new Program();
            // Load skin
            app.LoadSkin();

            MainWindow m = new MainWindow(Settings.Default);
            m.BeginInit();

            Uri u = new Uri("pack://application:,,,/paperboywin.ico", UriKind.RelativeOrAbsolute);
            BitmapDecoder bd = BitmapDecoder.Create(u, BitmapCreateOptions.None, BitmapCacheOption.None);
            BitmapFrame frame = bd.Frames[0];

            m.Icon = frame;
            m.Closed += new EventHandler(MainWindow_Closed);
            m.Loaded += new RoutedEventHandler(MainWindow_Loaded);
            m.EndInit();

            app.Run(m);
        }

        private static void MainWindow_Loaded(object sender, RoutedEventArgs e)
        {
            splashScreen.Close();
        }

        private static void MainWindow_Closed(object sender, EventArgs e)
        {
            Settings.Default.Save();
        }

        public Program()
        {
            //AppDomain.CurrentDomain.UnhandledException += new UnhandledExceptionEventHandler(CurrentDomain_UnhandledException);
            //Dispatcher.UnhandledExceptionFilter += new System.Windows.Threading.DispatcherUnhandledExceptionFilterEventHandler(Dispatcher_UnhandledExceptionFilter);
            this.DispatcherUnhandledException += new System.Windows.Threading.DispatcherUnhandledExceptionEventHandler(App_DispatcherUnhandledException);
        }

        void Dispatcher_UnhandledExceptionFilter(object sender, System.Windows.Threading.DispatcherUnhandledExceptionFilterEventArgs e)
        {
            bool skip = FilterException(e.Exception);
            e.RequestCatch = !skip;
        }

        void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e)
        {
            if (e.ExceptionObject is Exception)
                HandleFatalException((Exception)e.ExceptionObject);
        }

        void App_DispatcherUnhandledException(object sender, System.Windows.Threading.DispatcherUnhandledExceptionEventArgs e)
        {
            // Hack...
            bool skip = FilterException(e.Exception);

            if (skip)
                e.Handled = true;
            else
                e.Handled = HandleFatalException(e.Exception);
        }

        static bool FilterException(Exception e)
        {
            return (String.Compare(e.Message, "Cannot read from the stream.", true) == 0 || e is ObjectDisposedException);
        }

        private static bool HandleFatalException(Exception ex)
        {
            try
            {
                ExceptionManager.FatalError(ex);

                return true;
            }
            catch (Exception)
            {
                MessageBox.Show("Fatal error", "PaperBoy", MessageBoxButton.OK, MessageBoxImage.Error);
                return false;
            }
        }

        private void LoadSkin()
        {
            Ricciolo.PaperBoy.UI.ISkin skin = null;
            // TODO: load saved skin
            if (skin == null)
                skin = new Ricciolo.PaperBoy.Themes.Classic.Skins.DefaultSkin();
            //skin = new Ricciolo.PaperBoy.Themes.Classic.Skins.SimpleSkin();

            // Add skin resouces
            this.Resources.MergedDictionaries.Add(skin.ApplicationResources);
        }
    }
}